<template>
  <div class="app-container">
    <FilterSearch class="filter-search" :value="queryParams" :labelCol="{ span: 6 }" :wrapperCol="{ span: 18 }"
      :config="configData" labelWidth="120px" position="right"></FilterSearch>
    <div class="main">
      <div class="table">
        <el-table stripe @selection-change="selectionChange" :data="tableData.rows" border v-loading="tableData.loading"
          style="width: 100%">
          <el-table-column type="selection" width="55" />
          <el-table-column prop="id" label="ID" width="55">
          </el-table-column>
          <el-table-column prop="sqlName" label="原始数据名称" width="200">
          </el-table-column>
          <el-table-column prop="sqlContent" label="抽数sql" min-width="450">
            <template v-slot="scope">
              <el-popover placement="top-start" :width="500" trigger="hover">
                <div style="max-height: 150px;">
                  <el-scrollbar :height="150">
                    {{ scope.row.sqlContent }}
                  </el-scrollbar>
                </div>
                <template #reference>
                  <div class="ellipsis_3">
                    {{ scope.row.sqlContent }}
                  </div>
                </template>
              </el-popover>
            </template>
          </el-table-column>
          <el-table-column prop="diffField" label="差分字段" width="100">
          </el-table-column>
          <el-table-column prop="diffVal" label="差分值" width="100">
          </el-table-column>
          <el-table-column prop="uid" label="创建者" width="100">
          </el-table-column>
          <el-table-column prop="createdTime" label="创建时间" width="160">
            <template v-slot="scope">
              <div>
                {{ getDate(scope.row.createdTime) }}
              </div>
            </template>
          </el-table-column>
          <el-table-column prop="updateTime" label="修改时间" width="160">
            <template v-slot="scope">
              <div>
                {{ getDate(scope.row.updateTime) }}
              </div>
            </template>
          </el-table-column>
          <el-table-column fixed="right" label="操作" width="140">
            <template v-slot="scope">
              <el-button @click="handleClick(scope.row, 'update')" type="text" size="small">编辑</el-button>
              <el-button @click="handleClick(scope.row, 'copy')" type="text" size="small">复制</el-button>
            </template>
          </el-table-column>
        </el-table>
      </div>
      <div class="page">
        <el-pagination @current-change="currentChange" layout="total, prev, pager, next, jumper" :total="tableData.total"
          :current-page="queryParams.currentPage">
        </el-pagination>
      </div>
    </div>
    <el-dialog v-model="rowData.diaVis" :title="rowData.formTit" width="900px" :close-on-click-modal="false"
      :show-close="false">
      <div class="box-container">
        <el-form label-position="left" :rules="formRule" ref="formState" :model="rowData.formInline" label-width="170px">
          <el-form-item label="请输入原始数据名称:" prop="sqlName">
            <div class="col">
              <el-input @change="originalNameRules" v-model="rowData.formInline.sqlName" placeholder="请输入原始数据名称" />
            </div>
          </el-form-item>
          <el-form-item label="请选择数据库:" prop="dataBaseConfigId">
            <div class="col">
              <el-select v-model="rowData.formInline.dataBaseConfigId" placeholder="请选择数据库">
                <el-option v-for="(item, ind) in dataBase" :key="item.id" :label="item.info" :value="item.id">
                </el-option>
              </el-select>
            </div>
          </el-form-item>
          <!-- <el-form-item label="请输入组合索引字段名:" prop="index_columns">
            <el-input v-model="rowData.formInline.index_columns" placeholder='定义多个字段以 " , " 隔开' />
          </el-form-item> -->
          <el-form-item label="请输入抽数SQL:" prop="sqlContent">
            <div class="tips">
              <div class="text">
                注:请定义差分条件,例如 'myid > #myid#'
              </div>
              <div class="btns">
                <div class="btn" @click="formatSQLFnc">
                  SQL格式化
                </div>
                <div class="btn" @click="formatSQLValid">
                  SQL效验
                </div>
              </div>
            </div>
            <el-input v-model="rowData.formInline.sqlContent" placeholder="请输入抽数SQL" resize="none" :rows="10"
              type="textarea" />
          </el-form-item>
          <el-form-item label="请输入差分字段:">
            <el-input v-model="rowData.formInline.diffField" placeholder='定义多个字段以 " , " 隔开' />
          </el-form-item>
          <el-form-item label="请输入差分字段初始值:">
            <el-input v-model="rowData.formInline.diffVal" placeholder='定义多个字段以 " , " 隔开' />
          </el-form-item>
        </el-form>
      </div>
      <template #footer>
        <span class="dialog-footer">
          <el-button @click="cancel">取消</el-button>
          <el-button type="primary" @click="submit">
            确认
          </el-button>
        </span>
      </template>
    </el-dialog>
  </div>
</template>

<script>
import { ElMessage } from 'element-plus'
import { ref, reactive, computed, onBeforeMount, onBeforeUnmount } from "vue"
import {
  getList, getDatabase, insertRow, selectOne, formatSQL, updateRow
  , delateRow, insertRules, validateSQL
} from "@/api/originalData.js"
import { formatDate } from "@/utils/index.js"
import { formData } from "@/utils/validate.js"
export default {
  setup() {
    const { proxy } = getCurrentInstance();

    const tableData = reactive({
      rows: [
        {
          importID: 1,
          id: 1,
          sqlname: '特试探试探洒水大大声',
          sqldesc: "sdasdasdasdasdasdd",
          sqlcontent: "qweqeqeqeqwqeqweqwe",
          publisher: "qweqeasdteqweqe",
          createTime: "2023/11/04 15:08:09",
          updateTime: "2023/12/11 16:05:39",
          deleteflg: "13qeqeeqeqeqeeew"
        },
        {
          importID: 2,
          id: 2,
          sqlname: '特试探试探洒水大大声',
          sqldesc: "sdasdasdasdasdasdd",
          sqlcontent: "qweqeqeqeqwqeqweqwe",
          publisher: "qweqeasdteqweqe",
          createTime: "2023/11/04 15:08:09",
          updateTime: "2023/12/11 16:05:39",
          deleteflg: "13qeqeeqeqeqeeew"
        },
        {
          importID: 3,
          id: 3,
          sqlname: '特试探试探洒水大大声',
          sqldesc: "sdasdasdasdasdasdd",
          sqlcontent: "qweqeqeqeqwqeqweqwe",
          publisher: "qweqeasdteqweqe",
          createTime: "2023/11/04 15:08:09",
          updateTime: "2023/12/11 16:05:39",
          deleteflg: "13qeqeeqeqeqeeew"
        }
      ],
      total: 0,
      loading: false,
      selection: []
    });
    const dataBase = ref([]);
    const queryParams = ref({
      currentPage: 1,
      size: 10,
      sqlName: ""
    });
    const rowData = reactive({
      diaVis: false,
      formInline: {},
      formTit: "创建原始数据",
      status: 0,
      sqlNameStatus: false,
      submitStatus: false
    })

    const configData = computed(() => {
      let config = {
        itemConfig: [
          {
            type: "input",
            prop: "sqlName",
            clearable: "关闭",
            label: "原始数据名称",
            placeholder: "请输入",
          }
        ],
        operate: [
          {
            icon: "Search",
            type: "primary",
            name: "查询",
            handleClick: getLoad,
            rule: true,
          },
          {
            icon: "RefreshLeft",
            type: "primary",
            name: "重置",
            handleClick: reset,
            rule: true,
          },
          {
            icon: "Plus",
            type: "primary",
            name: "新增",
            handleClick: insert,
            rule: true,
          },
          {
            icon: "Delete",
            type: "primary",
            name: "批量删除",
            handleClick: allDel,
            rule: true,
          }
        ],
        rules: {},
      };
      return config;
    })
    const timeOut = {
      setTime1: null,
      setTime2: null,
      setTime3: null,
    };
    const validateSqlName = (rule, value, callback) => {
      if (proxy.rowData.sqlNameStatus) {
        callback(new Error("原始数据名称已重复,请修改"));
      } else {
        callback();
      }
    };
    const formRule = computed(() => {
      let rules = {
        sqlName: [
          { required: true, trigger: "blur", message: "请输入原始数据名称" },
          { required: true, trigger: "change", message: "请输入原始数据名称" },
          {
            validator: validateSqlName,
            trigger: "change",
          },
          {
            validator: validateSqlName,
            trigger: "blur",
          },
        ],
        dataBaseConfigId: [
          { required: true, trigger: "blur", message: "请选择数据库" },
          { required: true, trigger: "change", message: "请选择数据库" },
        ],
        index_columns: [
          { required: true, trigger: "blur", message: "请输入组合索引字段名" },
          { required: true, trigger: "change", message: "请输入组合索引字段名" },
        ],
        sqlContent: [
          { required: true, trigger: "blur", message: "请输入抽象sql" },
          { required: true, trigger: "change", message: "请输入抽象sql" },
        ]
      };
      return rules;
    })
    const getDate = (date) => {
      return formatDate(date)
    }
    const currentChange = (page) => {
      proxy.queryParams.currentPage = page;
      getLoad();
    }
    const getLoad = () => {
      proxy.tableData.loading = true;
      getList(proxy.queryParams).then(res => {
        proxy.tableData.loading = false;
        if (res.status == 'success') {
          ElMessage.success('查询成功');
        } else {
          ElMessage.error('查询失败');
          return;
        }
        proxy.tableData.rows = res.data.records;
        proxy.tableData.total = res.data.total;
      })
    }
    const insert = () => {
      proxy.rowData.diaVis = true;
      proxy.rowData.status = 0;
      proxy.rowData.formTit = "新增原始数据";
      proxy.rowData.formInline = {};
    }
    const reset = () => {
      proxy.queryParams.pageNum = 10;
      proxy.queryParams.currentPage = 1;
      proxy.queryParams.sqlName = "";
      getLoad();
    }
    const submit = () => {
      if (!proxy.rowData.submitStatus) {
        ElMessage.info('请先校验SQL');
        return;
      }
      proxy.$refs.formState.validate(valid => {
        if (valid) {
          let status = proxy.rowData.status;
          switch (status) {
            case 0:
              insertRow(JSON.stringify(proxy.rowData.formInline)).then(res => {
                if (res.status == 'success') {
                  ElMessage.success(res.msg);
                  cancel();
                } else {
                  ElMessage.error(res.msg);
                }
                getLoad();
              })
              break;
            case 1:
              updateRow(JSON.stringify(proxy.rowData.formInline)).then(res => {
                if (res.status == 'success') {
                  ElMessage.success(res.msg);
                  cancel();
                } else {
                  ElMessage.error(res.msg);
                }
                getLoad();
              })
              break;
            case 2:
              insertRow(JSON.stringify(proxy.rowData.formInline)).then(res => {
                if (res.status == 'success') {
                  ElMessage.success(res.msg);
                  cancel();
                } else {
                  ElMessage.error(res.msg);
                }
                getLoad();
              })
              break;
            default:
              break;
          }

        }
      })

    }
    const cancel = () => {
      proxy.rowData.formInline = {};
      timeOut.setTime1 = setTimeout(() => {
        proxy.$refs.formState.clearValidate();
        proxy.rowData.diaVis = false;
        proxy.rowData.submitStatus = false;
      }, 100);
    }
    const originalNameRules = () => {

      if (!proxy.rowData.formInline.sqlName) {
        proxy.rowData.sqlNameStatus = false;
        timeOut.setTime2 = setTimeout(() => {
          proxy.$refs.formState.validateField("sqlName");
        }, 100);
        return;
      }

      insertRules(proxy.rowData.formInline.sqlName).then(res => {
        if (res.data) {
          proxy.rowData.sqlNameStatus = true;
        } else {
          proxy.rowData.sqlNameStatus = false;
        }
        timeOut.setTime3 = setTimeout(() => {
          proxy.$refs.formState.validateField("sqlName");
        }, 100);
      })
    }
    const formatSQLFnc = () => {
      let row = proxy.rowData.formInline.sqlContent;
      if (row && row != null && row != "" && row != undefined) {
        formatSQL(formData({ sqlContent: row })).then(res => {
          if (res.status == 'success') {
            ElMessage.success('格式化成功');
          } else {
            ElMessage.error('格式化失败');
            return;
          }
          proxy.rowData.formInline.sqlContent = res.data;
        })
      }
    }
    const formatSQLValid = () => {
      proxy.$refs.formState.validateField("dataBaseConfigId");
      proxy.$refs.formState.validateField("dataBaseConfigId");
      if ((!proxy.rowData.formInline.diffField && proxy.rowData.formInline.diffVal) || (proxy.rowData.formInline.diffField && !proxy.rowData.formInline.diffVal)) {
        ElMessage.info("请传入差分字段,初始值或都不填");
        return;
      }
      if (!proxy.rowData.formInline.dataBaseConfigId) {
        return;
      }
      if (!proxy.rowData.formInline.dataBaseConfigId) {
        return;
      }
      let param = {
        dataBaseConfigId: rowData.formInline.dataBaseConfigId,
        sqlContent: rowData.formInline.sqlContent,
        diffField: rowData.formInline.diffField,
        diffVal: rowData.formInline.diffVal,
      }
      validateSQL(JSON.stringify(param)).then(res => {
        let row = JSON.parse(res.data);
        if (row.CODE == 1) {
          proxy.rowData.submitStatus = true;
          ElMessage.success(row.MESSAGE);
        } else {
          ElMessage.error(row.MESSAGE);
        }
      })
    }
    const selectionChange = (selection) => {
      proxy.tableData.selection = selection;
    }
    const allDel = () => {
      if (proxy.tableData.selection.length <= 0) {
        ElMessage.info('请选择数据');
        return;
      }
      let ids = proxy.tableData.selection.map(it => {
        return it.id;
      })
      delateRow(formData({ ids })).then(res => {
        if (res.status == 'success') {
          ElMessage.success(res.msg);
          getLoad();
        } else {
          ElMessage.error('删除失败');
          return;
        }
      })
    }

    const handleClick = (row, type) => {
      switch (type) {
        case 'update':
          selectOne(row).then(res => {
            proxy.rowData.formInline = res.data;

            proxy.rowData.diaVis = true;
            proxy.rowData.formTit = "编辑原始数据";
            proxy.rowData.status = 1;
            proxy.rowData.submitStatus = false;
          })
          break;
        case 'delete':

          break;
        case 'copy':
          selectOne(row).then(res => {
            proxy.rowData.formInline = res.data;
            proxy.rowData.formInline.id = null;
            proxy.rowData.formInline.sqlName = null;
            
            proxy.rowData.diaVis = true;
            proxy.rowData.formTit = "复制原始数据";
            proxy.rowData.status = 2;
            proxy.rowData.submitStatus = false;
          })
          break;
        default:
          break;
      }
    }
    onBeforeMount(() => {
      getLoad();
      getDatabase().then(res => {
        proxy.dataBase = res.data;
      })
    })
    onBeforeUnmount(() => {
      for (const key in timeOut) {
        if (timeOut[key]) {
          clearTimeout(timeOut[key]);
        }
      }
    })
    return {
      tableData, queryParams, configData, rowData, dataBase,
      currentChange, selectionChange, insert, reset, submit, getDate, formatSQLFnc, handleClick, cancel,
      formRule, originalNameRules, formatSQLValid
    }
  }
}
</script>
<style lang="scss" scoped>
.main {
  .page {
    padding: 10px 0;
    float: right;
  }
}

.box-container {
  .col {
    display: flex;
    width: 100%;

    .el-input {
      width: 100%;
      margin-right: 10px;
    }

    .el-select {
      width: 100%;
      margin-right: 10px;
    }
  }

  .tips {
    width: 100%;
    display: flex;
    flex-direction: row;
    justify-content: space-between;
    align-items: center;
    font-size: 12px;
    padding: 0 5px;
    background-color: #d9ecff;
    border-top-left-radius: 5px;
    border-top-right-radius: 5px;

    .btns {
      display: flex;
      flex-direction: row;
      align-items: center;
      margin: 5px 0;

      .btn {
        border: solid 1px #000000;
        padding: 0px 10px;
        border-radius: 5px;
        margin-left: 10px;
        line-height: 25px;
        color: #409EFF;
        color: #000000;

        &:hover {
          border: solid 1px #409EFF;
          cursor: pointer;
          color: #409EFF;
        }
      }
    }
  }
}

.ellipsis_3 {
  overflow: hidden;
  text-overflow: ellipsis;
  display: -webkit-box;
  -webkit-line-clamp: 3;
  -webkit-box-orient: vertical;
}
</style>